package com.djmw.mouse.service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.domain.Sort.Direction;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import com.djmw.mouse.entity.PositionType;
import com.djmw.mouse.entity.PositionTypeNode;
import com.djmw.mouse.repository.PositionTypeDao;

//Spring Bean的标识.
@Component
// 默认将类中的所有public函数纳入事务管理.
@Transactional(readOnly = true)
public class PositionTypeService {

    private static Logger logger = LoggerFactory.getLogger(PositionTypeService.class);

    @Autowired
    private PositionTypeDao positionTypeDao;

    private List<PositionTypeNode> allPositionTypesTree;

    public PositionType getPosition(Long id) {
        return positionTypeDao.findOne(id);
    }

    @Transactional(readOnly = false)
    public PositionType savePosition(PositionType entity) {
        return positionTypeDao.save(entity);
    }

    @Transactional(readOnly = false)
    public void deletePosition(Long id) {
        PositionType position = positionTypeDao.findOne(id);
        if (position != null) {
            if (position.getLevel() == 1) {
                // Level 1 position
                positionTypeDao.deleteLevelOnePosition(id);
            } else if (position.getLevel() == 2) {
                // Level 2 position
                positionTypeDao.deleteLevelTwoPosition(id);
            } else {
                // Level 3 position
                positionTypeDao.delete(id);
            }
        }
    }

    @Transactional(readOnly = false)
    public void deleteLevelOnePosition(Long id) {
        positionTypeDao.deleteLevelOnePosition(id);
    }

    @Transactional(readOnly = false)
    public void deleteLevelTwoPosition(Long id) {
        positionTypeDao.deleteLevelTwoPosition(id);
    }

    public List<PositionType> getAllPositionTypes() {
        return (List<PositionType>) positionTypeDao.findAll(new Sort(Direction.ASC, "order"));
    }

    public List<PositionTypeNode> getAllPositionTypesTree() {
        if (allPositionTypesTree == null) {
            synchronized (PositionTypeService.class) {
                List<PositionType> allPositionTypes = getAllPositionTypes();
                allPositionTypesTree = new ArrayList<PositionTypeNode>();
                HashMap<PositionType, PositionTypeNode> map = new HashMap<PositionType, PositionTypeNode>();
                for (PositionType positionType : allPositionTypes) {
                    PositionTypeNode node = new PositionTypeNode(positionType);
                    PositionType parent = findParent(allPositionTypes, positionType);
                    if (parent == null) {
                        allPositionTypesTree.add(node);
                    } else {
                        PositionTypeNode parentNode = map.get(parent);
                        if (parentNode != null) {
                            parentNode.addSubPositionType(node);
                        } else {
                            logger.info(parent.getId() + ", " + parent.getName());
                        }
                    }
                    if (positionType.getLevel() != 3) {
                        map.put(positionType, node);
                    }
                }
            }
        }
        return allPositionTypesTree;
    }

    private PositionType findParent(List<PositionType> allPositionTypes, PositionType positionType) {
        int level = positionType.getLevel();
        if (level == 1) {
            return null;
        }
        int id = level == 2 ? positionType.getLevel1Id() : positionType.getLevel2Id();
        for (PositionType node : allPositionTypes) {
            if (node.getId() == id) {
                return node;
            }
        }
        return null;
    }
}
